<template>
  <div id="container"></div>
</template>

<script>
import AMapLoader from "@amap/amap-jsapi-loader";
import { getequipmentlist } from '@/api/echarts';

export default {
  name: "map-view",
  data() {
    return {
      map: null,
      points: [],
      clusterData: [],
      districtBoundaries: {},
    };
  },
  created() {
    this.fetchEquipmentList();
  },
  mounted() {
    this.initAMap();
  },
  unmounted() {
    this.map?.destroy();
  },
  methods: {
    async fetchEquipmentList() {
      try {
        const res = await getequipmentlist({ limit: 10000000 });
        this.points = res.msg
          .filter(item => item.lat && item.lng)
          .map(item => ({
            lnglat: [parseFloat(item.lng), parseFloat(item.lat)],
          }));

        // 获取区级边界
        await this.fetchDistrictBoundaries();

        // 进行聚合
        this.aggregatePoints();

        // 初始化聚合显示
        if (this.map) {
          this.initCluster();
        }
      } catch (error) {
        console.error('Error fetching equipment list:', error);
      }
    },
    async fetchDistrictBoundaries() {
      return new Promise((resolve, reject) => {
        AMapLoader.load({
          key: "f8c954755588cd09132500151dc4d01c",
          version: "2.0",
          plugins: ["AMap.DistrictSearch"],
        }).then(AMap => {
          const districtSearch = new AMap.DistrictSearch({
            level: 'district',
            showBoundary: true,
          });
          
          districtSearch.search('全国', (status, result) => {
            if (status === 'complete' && result.info === 'OK') {
              this.districtBoundaries = result.districtList.reduce((acc, district) => {
                acc[district.name] = district.boundaries[0];
                return acc;
              }, {});
              resolve();
            } else {
              reject(result.info);
            }
          });
        }).catch(error => {
          reject(error);
        });
      });
    },
    aggregatePoints() {
      this.clusterData = Object.entries(this.districtBoundaries).map(([district, boundaries]) => {
        const pointsInDistrict = this.points.filter(point => {
          return AMap.GeometryUtil.isPointInPolygon(point.lnglat, new AMap.Polygon({ path: boundaries }));
        });

        return {
          district,
          points: pointsInDistrict,
          count: pointsInDistrict.length,
        };
      });
    },
    initAMap() {
      AMapLoader.load({
        key: "f8c954755588cd09132500151dc4d01c",
        version: "2.0",
        plugins: ["AMap.Scale", "AMap.MarkerClusterer", "AMap.Geolocation"],
      }).then(AMap => {
        this.map = new AMap.Map("container", {
          viewMode: "3D",
          zoom: 4,
          center: [116.397428, 39.90923],
          mapStyle: "amap://styles/blue",
        });

        this.map.addControl(new AMap.Scale());

        this.map.plugin('AMap.Geolocation', () => {
          const geolocation = new AMap.Geolocation({
            enableHighAccuracy: true,
            timeout: 10000,
            buttonOffset: new AMap.Pixel(10, 20),
            zoomToAccuracy: true,
          });
          this.map.addControl(geolocation);
          geolocation.getCurrentPosition((status, result) => {
            if (status === 'complete') {
              this.map.setCenter(result.position);
            } else {
              console.error('Geolocation failed: ', result.message);
            }
          });
        });

        this.initCluster();
      }).catch(error => {
        console.log(error);
      });
    },
    initCluster() {
      if (this.cluster) {
        this.cluster.setMap(null);
      }
      const markers = this.clusterData.map(cluster => {
        return new AMap.Marker({
          position: this.calculateClusterPosition(cluster.district),
          map: this.map,
          content: `<div class="amap-cluster">${cluster.count}</div>`,
        });
      });

      this.cluster = new AMap.MarkerClusterer(this.map, markers, {
        gridSize: 80,
      });
    },
    calculateClusterPosition(district) {
      const boundaries = this.districtBoundaries[district];
      if (boundaries && boundaries.length) {
        const lngs = boundaries.map(p => p[0]);
        const lats = boundaries.map(p => p[1]);
        return new AMap.LngLat(
          (Math.max(...lngs) + Math.min(...lngs)) / 2,
          (Math.max(...lats) + Math.min(...lats)) / 2
        );
      }
      return [116.397428, 39.90923]; // 默认位置
    },
  },
};
</script>

<style scoped>
#container {
  width: 100%;
  height: 100%;
}
.amap-cluster {
  display: flex;
  justify-content: center;
  align-items: center;
  font-size: 14px;
  color: #fff;
  background: rgba(51,153,255,0.6);
  border-radius: 50%;
  width: 40px;
  height: 40px;
  text-align: center;
  line-height: 40px;
}
</style>
